#coding=utf-8
import platform
import getpass
import _tkinter ## import Tkinter as tk
import tkinter as tk ##
from tkinter import *
from tkinter import ttk
import tkinter.filedialog
import tkinter.messagebox
from selenium import webdriver
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
import random
import sys
import threading
import requests
# 下面几个包都是FirefoxProfile需要的
import copy
import json
import tempfile
import shutil
import os
import queue ## import Queue
# 这里将该json文件里的内容都放到了我们的脚本里，你也可以放到另一个py文件中import进来

## other libraries for login
from selenium.webdriver import ActionChains
from selenium.webdriver.common.by import By
import time
from urllib.request import urlretrieve
from PIL import Image

if platform.system() == "Windows":
	doc_path = ''
else:
	doc_path = u"/Users/{}/Documents".format(getpass.getuser())
	try:
		os.path.join(doc_path, u'陈意涵')
		os.mkdir(doc_path+u'/陈意涵')
	except Exception as e:
		pass
	doc_path = doc_path+u'/陈意涵/'

home_url='https://v.qq.com/x/star/1661556?tabid=3'

class DokiLogin(object):
	def __init__(self, object):
		self.home_url = 'https://v.qq.com/x/star/1661556?tabid=3'
		## self.driver = webdriver.Chrome(executable_path = os.getcwd() + '/chromedriver')
		self.driver = object.driver
		self.status = object.status
		self.to_continue = False
		self.frozen_count = 0
		self.wait_l = WebDriverWait(self.driver, 10)
		self.wait_s = WebDriverWait(self.driver, 1)

	# def get_account_info(self, filename):
	# 	try:
	# 		f = open(filename, 'r')
	# 		accounts = {}
	# 		for line in f:
	# 			user, pw = line.strip().split('----')
	# 			accounts[user] = pw
	# 		return accounts
	# 	except Exception:
	# 		print("获取帐号失败！")

	def is_login(self):
		try:
			self.driver.switch_to.default_content()
			#print(self.wait_s.until(EC.presence_of_element_located((By.CLASS_NAME, "account_type"))))
			return self.wait_s.until(EC.presence_of_element_located((By.CLASS_NAME, "account_type"))).get_attribute("style") != "display: none;"
		except:
			return False


	def download_images(self, bg):
		bg_url = bg.get_attribute("src")
		fullbg_url = "https://hy.captcha.qq.com/hycdn_0" + bg_url.split("https://hy.captcha.qq.com/hycdn_1")[1]
		try:
			os.path.join(doc_path, 'Image')
			os.mkdir(doc_path+'/Image')
		except Exception as e:
			pass

		# if not os.path.exists('Image'):
		# 	os.mkdir('Image')
		urlretrieve(url=fullbg_url, filename=doc_path+'Image/fullbg.jpg')
		#print('原始背景图片下载完成！')
		urlretrieve(url=bg_url, filename=doc_path+'Image/bg.jpg')
		#print('背景图片下载完成！')

	def is_px_equal(self, img1, img2, x, y):
		pix1 = img1.load()[x,y]
		pix2 = img2.load()[x,y]
		threshold = 60
		if abs(pix1[0]-pix2[0]) < threshold and abs(pix1[1]-pix2[1]) < threshold and abs(pix1[2]-pix2[2]) < threshold:
			return True
		else:
			return False

	def get_gap(self, img1, img2):
		left = 300
		for i in range(left, img1.size[0]):
			for j in range(img1.size[1]):
				if not self.is_px_equal(img1, img2, i, j):
					left = i
					return left
		return left

	def cal_dist(self, bg):
		im1 = Image.open(doc_path+'Image/fullbg.jpg')
		im2 = Image.open(doc_path+'Image/bg.jpg')
		scale = bg.size.get("width")/im2.size[0]
		distance = (self.get_gap(im1, im2) * 1. * scale) - 12
		return distance

	def get_track(self, distance):
		# 移动轨迹
		tracks = []
		# 当前位移
		current = 0
		# 减速阈值
		mid = distance * 2 / 5
		mid2 = distance * 3 / 4
		# 随机系数
		# ri = random.uniform(0.7, 1)
		# 时间间隔
		t = 0.2
		# 初始速度
		v = 0

		while current < distance:
			if current < mid:
				a = random.uniform(10, 12)
			elif current < mid2:
				a = random.uniform(1, 2)
			else:
				a = -(random.uniform(12.5, 13.5))
			v0 = v
			v = v0 + a * t
			x = v0 * t + 1 / 2 * a * t * t
			current += x

			if 0.6 < current - distance < 1:
				x = x - 0.53
				tracks.append(round(2*x, 2))

			elif 1 < current - distance < 1.5:
				x = x - 1.4
				tracks.append(round(2*x, 2))
			elif 1.5 < current - distance < 3:
				x = x - 1.8
				tracks.append(round(2*x, 2))
			elif 3 < current - distance < 5:
				x = x - 4
				tracks.append(round(2*x, 2))
			elif 5 < current - distance < 7:
				x = x - 6
				tracks.append(round(2*x, 2))
			else:
				tracks.append(round(2*x, 2))

		return tracks



	def captcha_check(self):
		self.driver.switch_to.default_content()
		self.wait_l.until(EC.frame_to_be_available_and_switch_to_it((By.ID, "_login_frame_quick_")))
		#time.sleep(0.5)
		#self.driver.switch_to.frame(self.driver.find_element_by_tag_name("iframe"))
		self.wait_l.until(EC.frame_to_be_available_and_switch_to_it((By.CSS_SELECTOR, "iframe")))
		bg = self.wait_l.until(EC.presence_of_element_located((By.ID, "slideBkg")))
		self.download_images(bg)

		distance = self.cal_dist(bg)
		slider = self.wait_l.until(EC.element_to_be_clickable((By.ID, "tcaptcha_drag_button")))
		tracks = self.get_track(distance/2)

		times = 0
		while times < 3:
			action = ActionChains(self.driver)
			action.click_and_hold(slider).perform()
			action.reset_actions()

			for x in tracks:
				action.move_by_offset(xoffset=x,yoffset=-0.2).perform()
				action.reset_actions()
			time.sleep(0.5)
			action.release().perform()

			try:
				alert = self.wait_s.until(EC.presence_of_element_located((By.CSS_SELECTOR, ".tcaptcha-title"))).text
			except Exception as e:
				alert = ''
			if alert:
				#print('滑块位移需要调整：%s' % alert)
				distance -= 1
				times += 1
			else:
				#print('滑块验证通过')
				return True

		if times == 3:
			#print("验证码尝试不成功")
			return False


	def check_frozen(self):
		self.driver.switch_to.default_content()
		try:
			self.wait_l.until(EC.frame_to_be_available_and_switch_to_it((By.ID, "_login_frame_quick_")))
			self.wait_s.until(EC.presence_of_element_located((By.LINK_TEXT, "点击这里")))
			return True
		except Exception:
			return False


	def frame_relogin(self, user, pw):
		if self.is_login():
			#print("帐号" + str(user) + "已成功登录！")
			self.to_continue = True
			return True
		try:
			self.driver.switch_to.default_content()
			self.wait_l.until(EC.frame_to_be_available_and_switch_to_it((By.ID, "_login_frame_quick_")))
			p = self.wait_l.until(EC.presence_of_element_located((By.ID, "p")))
			p.clear()
			time.sleep(0.2)


			for x in pw:
				p.send_keys(x)
				time.sleep(random.uniform(0.2, 0.3))
			time.sleep(0.2)
			self.wait_l.until(EC.element_to_be_clickable((By.ID, "login_button"))).click()
			time.sleep(1)
		except Exception as e:
			pass
		try:
			if self.check_frozen():
				self.write_frozen_account(user, pw)
				#print("帐号" + str(user) + "已被冻结！\n")
				self.driver.delete_all_cookies()
				self.driver.get(home_url)
				return True
			else:
				if self.captcha_check():
					if self.is_login():
						#print("帐号" + str(user) + "已成功登录！")
						self.to_continue = True
						return True
					else:
						return False
				else:
					return False
		except Exception:
			return False


	# def check_captcha_tab(self):
	#	 try:
	#		 self.driver.switch_to.frame("_login_frame_quick_")
	#		 time.sleep(0.5)
	#		 self.driver.switch_to.frame(self.driver.find_element_by_tag_name("iframe"))
	#		 return True
	#	 except Exception:
	#		 print("暂时无法登录")
	#		 return False


	def login(self, user, pw):
		#print(self.is_login())
		if self.is_login():
			#print("已登录")
			self.to_continue = True
			return True
		else:
			self.wait_l.until(EC.element_to_be_clickable((By.CSS_SELECTOR, '#mod_head_notice_trigger'))).click()
			self.wait_l.until(EC.element_to_be_clickable((By.CSS_SELECTOR, "._login_type_item"))).click()
			self.wait_l.until(EC.frame_to_be_available_and_switch_to_it((By.ID, "_login_frame_quick_")))
			self.wait_l.until(EC.element_to_be_clickable((By.LINK_TEXT, "帐号密码登录"))).click()
			u = self.wait_l.until(EC.presence_of_element_located((By.ID, "u")))
			for x in user:
				u.send_keys(x)
				time.sleep(random.uniform(0.2, 0.3))
			time.sleep(0.5)
			p = self.wait_l.until(EC.presence_of_element_located((By.ID, "p")))
			for x in pw:
				p.send_keys(x)
				time.sleep(random.uniform(0.2, 0.3))
			# self.wait_l.until(EC.presence_of_element_located((By.ID, "u"))).send_keys(user)
			# self.wait_l.until(EC.presence_of_element_located((By.ID, "p"))).send_keys(pw)
			self.wait_l.until(EC.element_to_be_clickable((By.ID, "login_button"))).click()
			time.sleep(0.5)
			if self.is_login():
				#print("帐号" + str(user) + "已成功登录！")
				self.to_continue = True
				return True
			else:
				if self.check_frozen():
					self.write_frozen_account(user, pw)
					#print("帐号" + str(user) + "已被冻结！\n")
					self.driver.delete_all_cookies()
					self.driver.get(home_url)
					return True
				else:
					try:
						if self.captcha_check():
							if self.is_login():
								#print("帐号" + str(user) + "已成功登录！")
								self.to_continue = True
								return True
							else:
								if self.check_frozen():
									self.write_frozen_account(user, pw)
									#print("帐号" + str(user) + "已被冻结！\n")
									self.driver.delete_all_cookies()
									self.driver.get(home_url)
									return True
								return False
						else:
							return False
					except Exception:
						#print("需重新尝试")
						return False

	def write_failed_account(self, user, pw):
		try:
			failed_account = open(doc_path+'密码错误帐号' + str(self.status) + '.txt', 'a+')
			failed_account.write(str(user) + "----" + str(pw))
			failed_account.write("\n")
			failed_account.close()
		except Exception:
			# print(doc_path)
			print("导出密码错误帐号失败")

	def write_frozen_account(self, user, pw):
		try:
			frozen_account = open(doc_path+'冻结帐号' + str(self.status) + '.txt', 'a+')
			frozen_account.write(str(user) + "----" + str(pw))
			frozen_account.write("\n")
			frozen_account.close()
			self.frozen_count += 1
		except Exception:
			print("导出冻结帐号失败")

	def write_success_account(self, user, pw):
		try:
			success_account = open(doc_path+'成功登录帐号' + str(self.status) + '.txt', 'a+')
			success_account.write(str(user) + "----" + str(pw))
			success_account.write("\n")
			success_account.close()
		except Exception:
			# print(doc_path)
			print("导出成功登录帐号失败")





